package com.pzhu.user.rpc.server;

import com.google.protobuf.Empty;
import com.pzhu.base.common.utils.exceptions.Assert;
import com.pzhu.user.api.UserApi;
import com.pzhu.user.api.UserServiceGrpc;
import com.pzhu.user.domain.dto.converter.UserDtoConverter;
import com.pzhu.user.domain.ro.UserCreateRO;
import com.pzhu.user.domain.ro.UserSearchRO;
import com.pzhu.user.domain.vo.RolePermissionCollectionVo;
import com.pzhu.user.domain.vo.UserSearchVO;
import com.pzhu.user.service.impl.RoleService;
import com.pzhu.user.service.impl.UserService;
import io.grpc.stub.StreamObserver;
import java.util.Optional;
import lombok.RequiredArgsConstructor;
import net.devh.boot.grpc.server.service.GrpcService;

@GrpcService
@RequiredArgsConstructor
public class UserServer extends UserServiceGrpc.UserServiceImplBase {

    private final UserService userService;

    private final RoleService roleService;

    private final UserDtoConverter userDtoConverter;

    @Override
    public void createUser(
            UserApi.CreateUserRequest request, StreamObserver<UserApi.CreateUserResponse> responseObserver) {
        UserApi.UserCreateDTO userCreateDTO = request.getUser();
        UserCreateRO userCreateRo = userDtoConverter.convert(userCreateDTO);
        Long userId = userService.createUser(userCreateRo);
        UserApi.CreateUserResponse.Builder builder = UserApi.CreateUserResponse.newBuilder();
        Optional.ofNullable(userId).ifPresent(builder::setUserId);
        responseObserver.onNext(builder.build());
        responseObserver.onCompleted();
    }

    @Override
    public void getUserById(UserApi.GetUserRequest request, StreamObserver<UserApi.UserResponse> responseObserver) {
        UserSearchRO userSearchRo = userDtoConverter.byIdConverter(request);
        doReturn(responseObserver, userSearchRo);
    }

    @Override
    public void getUserByUsername(
            UserApi.GetUserByUsernameRequest request, StreamObserver<UserApi.UserResponse> responseObserver) {
        UserSearchRO userSearchRo = userDtoConverter.byUserNameConverter(request);
        doReturn(responseObserver, userSearchRo);
    }

    private void doReturn(StreamObserver<UserApi.UserResponse> responseObserver, UserSearchRO userSearchRo) {
        UserSearchVO userSearchVO = userService.searchOne(userSearchRo);
        Assert.assertNotNull(userSearchVO,"用户不存在！");
        Long userId = userSearchVO.getUserId();
        RolePermissionCollectionVo userAllRoles = roleService.getUserAllRoles(userId);
        UserApi.UserDTO userDTO = userDtoConverter.searchRespToDTO(userSearchVO, userAllRoles);
        UserApi.UserResponse.Builder builder = UserApi.UserResponse.newBuilder();
        responseObserver.onNext(builder.setUser(userDTO).build());
        responseObserver.onCompleted();
    }

    @Override
    public void getUserByEmail(
            UserApi.GetUserByEmailRequest request, StreamObserver<UserApi.UserResponse> responseObserver) {
        UserSearchRO userSearchRo = userDtoConverter.byEmailConverter(request);
        doReturn(responseObserver, userSearchRo);
    }

    @Override
    public void getUserByPhone(
            UserApi.GetUserByPhoneRequest request, StreamObserver<UserApi.UserResponse> responseObserver) {
        UserSearchRO userSearchRo = userDtoConverter.byPhoneConverter(request);
        doReturn(responseObserver, userSearchRo);
    }

    @Override
    public void changePassword(UserApi.ChangePasswordRequest request, StreamObserver<Empty> responseObserver) {
        UserSearchVO userSearchVO = userService.searchOne(
                UserSearchRO.builder().username(request.getUsername()).build());
        Assert.assertNotNull(userSearchVO, "用户不存在");
        userService.changePassword(userSearchVO.getUserId(), request.getPassword());
        responseObserver.onNext(Empty.newBuilder().build());
        responseObserver.onCompleted();
    }

    @Override
    public void updateUser(UserApi.UpdateUserRequest request, StreamObserver<UserApi.UserResponse> responseObserver) {
        try {
            // 更新用户信息逻辑
            Long userId = request.getUserId();
            UserApi.UserUpdateDTO userUpdateDTO = request.getUser();
            
            // 这里需要实现具体的更新逻辑
            // userService.updateUser(userId, userUpdateDTO);
            
            // 返回更新后的用户信息
            UserSearchVO userSearchVO = userService.searchOne(
                    UserSearchRO.builder().userId(userId).build());
            Assert.assertNotNull(userSearchVO, "用户不存在");
            RolePermissionCollectionVo userAllRoles = roleService.getUserAllRoles(userId);
            UserApi.UserDTO userDTO = userDtoConverter.searchRespToDTO(userSearchVO, userAllRoles);
            
            UserApi.UserResponse.Builder builder = UserApi.UserResponse.newBuilder();
            responseObserver.onNext(builder.setUser(userDTO).build());
            responseObserver.onCompleted();
        } catch (Exception e) {
            responseObserver.onError(e);
        }
    }

    @Override
    public void deleteUser(UserApi.DeleteUserRequest request, StreamObserver<Empty> responseObserver) {
        try {
            Long userId = request.getUserId();
            // 这里需要实现删除用户逻辑
            // userService.deleteUser(userId);
            
            responseObserver.onNext(Empty.newBuilder().build());
            responseObserver.onCompleted();
        } catch (Exception e) {
            responseObserver.onError(e);
        }
    }

    @Override
    public void batchDeleteUsers(UserApi.BatchDeleteUsersRequest request, StreamObserver<Empty> responseObserver) {
        try {
            // 这里需要实现批量删除用户逻辑
            // userService.batchDeleteUsers(request.getUserIdsList());
            
            responseObserver.onNext(Empty.newBuilder().build());
            responseObserver.onCompleted();
        } catch (Exception e) {
            responseObserver.onError(e);
        }
    }

    @Override
    public void getAllUsers(UserApi.GetAllUsersRequest request, StreamObserver<UserApi.GetAllUsersResponse> responseObserver) {
        try {
            // 这里需要实现获取所有用户列表逻辑
            // List<UserSearchVO> users = userService.getAllUsers();
            // List<UserApi.UserDTO> userDTOs = users.stream()
            //         .map(user -> {
            //             RolePermissionCollectionVo userAllRoles = roleService.getUserAllRoles(user.getUserId());
            //             return userDtoConverter.searchRespToDTO(user, userAllRoles);
            //         })
            //         .collect(Collectors.toList());
            
            UserApi.GetAllUsersResponse.Builder builder = UserApi.GetAllUsersResponse.newBuilder();
            // builder.addAllUsers(userDTOs);
            
            responseObserver.onNext(builder.build());
            responseObserver.onCompleted();
        } catch (Exception e) {
            responseObserver.onError(e);
        }
    }
}